package cn.lngaosu.lwyd.module.integration.service.weixinvideolivedata;

import cn.hutool.core.collection.CollUtil;
import cn.lngaosu.lwyd.framework.common.util.http.HttpUtils;
import cn.lngaosu.lwyd.module.infra.service.config.ConfigService;
import cn.lngaosu.lwyd.module.integration.dal.dataobject.weixinvideoliverecord.WeixinvideoLiverecordDO;
import cn.lngaosu.lwyd.module.integration.dal.mysql.weixinvideoliverecord.WeixinvideoLiverecordMapper;
import cn.lngaosu.lwyd.module.integration.service.apptoken.AppTokenService;
import cn.lngaosu.lwyd.module.system.dal.dataobject.webinterfacelog.WebinterfaceLogDO;
import cn.lngaosu.lwyd.module.system.dal.mysql.webinterfacelog.WebinterfaceLogMapper;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.lang3.ObjectUtils;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Service;
import javax.annotation.Resource;
import org.springframework.validation.annotation.Validated;
import org.springframework.transaction.annotation.Transactional;

import java.time.LocalDateTime;
import java.util.*;
import cn.lngaosu.lwyd.module.integration.controller.admin.weixinvideolivedata.vo.*;
import cn.lngaosu.lwyd.module.integration.dal.dataobject.weixinvideolivedata.WeixinvideoLivedataDO;
import cn.lngaosu.lwyd.framework.common.pojo.PageResult;
import cn.lngaosu.lwyd.framework.common.pojo.PageParam;
import cn.lngaosu.lwyd.framework.common.util.object.BeanUtils;

import cn.lngaosu.lwyd.module.integration.dal.mysql.weixinvideolivedata.WeixinvideoLivedataMapper;

import static cn.lngaosu.lwyd.framework.common.exception.util.ServiceExceptionUtil.exception;
import static cn.lngaosu.lwyd.framework.common.util.collection.CollectionUtils.convertList;
import static cn.lngaosu.lwyd.framework.common.util.collection.CollectionUtils.diffList;
import static cn.lngaosu.lwyd.module.integration.enums.ErrorCodeConstants.*;

/**
 * 微信视频号直播大屏数据 Service 实现类
 *
 * @author 张恒
 */
@Service
@Validated
public class WeixinvideoLivedataServiceImpl implements WeixinvideoLivedataService {
    private static final Logger logger = LoggerFactory.getLogger(WeixinvideoLivedataServiceImpl.class);

    @Resource
    private WeixinvideoLivedataMapper weixinvideoLivedataMapper;
    @Resource
    private WeixinvideoLiverecordMapper weixinvideoLiverecordMapper;
    @Resource
    private AppTokenService appTokenService;
    @Resource
    private ConfigService configService;
    @Resource
    private WebinterfaceLogMapper webinterfaceLogMapper;

    @Override
    public Long createWeixinvideoLivedata(WeixinvideoLivedataSaveReqVO createReqVO) {
        // 插入
        WeixinvideoLivedataDO weixinvideoLivedata = BeanUtils.toBean(createReqVO, WeixinvideoLivedataDO.class);
        weixinvideoLivedataMapper.insert(weixinvideoLivedata);
        // 返回
        return weixinvideoLivedata.getId();
    }

    @Override
    public void updateWeixinvideoLivedata(WeixinvideoLivedataSaveReqVO updateReqVO) {
        // 校验存在
        validateWeixinvideoLivedataExists(updateReqVO.getId());
        // 更新
        WeixinvideoLivedataDO updateObj = BeanUtils.toBean(updateReqVO, WeixinvideoLivedataDO.class);
        weixinvideoLivedataMapper.updateById(updateObj);
    }

    @Override
    public void deleteWeixinvideoLivedata(Long id) {
        // 校验存在
        validateWeixinvideoLivedataExists(id);
        // 删除
        weixinvideoLivedataMapper.deleteById(id);
    }

    @Override
        public void deleteWeixinvideoLivedataListByIds(List<Long> ids) {
        // 校验存在
        validateWeixinvideoLivedataExists(ids);
        // 删除
        weixinvideoLivedataMapper.deleteByIds(ids);
        }

    private void validateWeixinvideoLivedataExists(List<Long> ids) {
        List<WeixinvideoLivedataDO> list = weixinvideoLivedataMapper.selectByIds(ids);
        if (CollUtil.isEmpty(list) || list.size() != ids.size()) {
            throw exception(WEIXINVIDEO_LIVEDATA_NOT_EXISTS);
        }
    }

    private void validateWeixinvideoLivedataExists(Long id) {
        if (weixinvideoLivedataMapper.selectById(id) == null) {
            throw exception(WEIXINVIDEO_LIVEDATA_NOT_EXISTS);
        }
    }

    @Override
    public WeixinvideoLivedataDO getWeixinvideoLivedata(Long id) {
        return weixinvideoLivedataMapper.selectById(id);
    }

    @Override
    public PageResult<WeixinvideoLivedataDO> getWeixinvideoLivedataPage(WeixinvideoLivedataPageReqVO pageReqVO) {
        return weixinvideoLivedataMapper.selectPage(pageReqVO);
    }

    @Override
    public void syncWeixinvideoLivedata() {
        // 接口配置
        String configValue = configService.getConfigValueByKey("weixinVideoConfig");
        if (StringUtils.isEmpty(configValue)) {
            throw exception(INTERFACE_CONFIG_NOT_EXISTS);
        }

        JSONObject configJo = JSONObject.parseObject(configValue);
        // 接口开关
        String onOff = configJo.getString("onOff");
        if (!"on".equals(onOff)) {
            throw exception(INTERFACE_CONFIG_NOT_EXISTS);
        }

        // 查询最近两天的直播记录数据
        LocalDateTime endDateTime = LocalDateTime.now();
        LocalDateTime beginDateTime = endDateTime.minusDays(2L);
        LambdaQueryWrapper<WeixinvideoLiverecordDO> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.between(WeixinvideoLiverecordDO::getCreateTime, beginDateTime, endDateTime);
        List<WeixinvideoLiverecordDO> weixinvideoLiverecordDOS = weixinvideoLiverecordMapper.selectList(queryWrapper);
        if (CollectionUtils.isEmpty(weixinvideoLiverecordDOS)) {
            return;
        }

        for (int i = 0; i < weixinvideoLiverecordDOS.size(); i++) {
            WeixinvideoLiverecordDO weixinvideoLiverecordDO = weixinvideoLiverecordDOS.get(i);
            String exportId = weixinvideoLiverecordDO.getExportId();
            // 获取token
            String weixinVideoToken = appTokenService.getWeixinVideoToken();
            if (StringUtils.isEmpty(weixinVideoToken)) {
                throw exception(WEIXINVIDEO_TOKEN_NOT_EXISTS);
            }
            // 获取地址
            String livedataUrl = configJo.getString("livedataUrl");
            livedataUrl = livedataUrl + "?access_token=" + weixinVideoToken;

            // 构造请求参数
            JSONObject params = new JSONObject();
            params.put("export_id", exportId);

            // 初始化日志数据（默认成功）
            WebinterfaceLogDO webinterfaceLogDO = new WebinterfaceLogDO();
            webinterfaceLogDO.setInterfaceSystemName("微信视频号");
            webinterfaceLogDO.setInterfaceName("获取直播大屏数据");
            webinterfaceLogDO.setInterfaceUrl(livedataUrl);
            webinterfaceLogDO.setInterfaceRequestMethod("POST");
            webinterfaceLogDO.setInterfaceParam(JSONObject.toJSONString(params));
            webinterfaceLogDO.setInterfaceStatus("成功");
            webinterfaceLogMapper.insert(webinterfaceLogDO);

            try {
                String result = HttpUtils.post(livedataUrl, new HashMap<>(), JSONObject.toJSONString(params));

                // 解析接口结果
                JSONObject resultJo = JSONObject.parseObject(result);
                Integer errcode = resultJo.getInteger("errcode");
                if (ObjectUtils.isNotEmpty(errcode) && errcode != 0) {
                    webinterfaceLogDO.setInterfaceStatus("失败");
                    webinterfaceLogDO.setInterfaceErrorInfo(result);
                    webinterfaceLogMapper.updateById(webinterfaceLogDO);
                    return;
                }
                webinterfaceLogDO.setInterfaceErrorInfo(result);
                webinterfaceLogMapper.updateById(webinterfaceLogDO);

                // 处理接口数据
                WeixinvideoLivedataDO weixinvideoLivedataDO = BeanUtils.toBean(resultJo, WeixinvideoLivedataDO.class);
                JSONObject liveDashboardDataJo1 = resultJo.getJSONObject("live_dashboard_data");
                JSONObject liveDashboardDataJo2 = liveDashboardDataJo1.getJSONObject("live_dashboard_data");
                JSONObject summaryJo = liveDashboardDataJo2.getJSONObject("summary");
                WeixinvideoLivedataDO weixinvideoLivedataDO1 = BeanUtils.toBean(summaryJo, WeixinvideoLivedataDO.class);
                BeanUtils.copyPropertiesIgnoreSourceNull(weixinvideoLivedataDO1, weixinvideoLivedataDO);
                weixinvideoLivedataDO.setStartTime(liveDashboardDataJo1.getLong("start_time"));
                weixinvideoLivedataDO.setLiveDuration(liveDashboardDataJo1.getLong("live_duration"));

                // 查询本地大屏数据是否存在，存在则更新，不存在则新增
                LambdaQueryWrapper<WeixinvideoLivedataDO> wrapper = new LambdaQueryWrapper<>();
                wrapper.eq(WeixinvideoLivedataDO::getExportId, exportId);
                List<WeixinvideoLivedataDO> weixinvideoLivedataDOS = weixinvideoLivedataMapper.selectList(wrapper);
                if (CollectionUtils.isNotEmpty(weixinvideoLivedataDOS)) {
                    weixinvideoLivedataDO.setId(weixinvideoLivedataDOS.get(0).getId());
                }

                weixinvideoLivedataMapper.insertOrUpdate(weixinvideoLivedataDO);
            } catch (Exception e) {
                webinterfaceLogDO.setInterfaceStatus("失败");
                webinterfaceLogDO.setInterfaceErrorInfo(e.getMessage());
                webinterfaceLogMapper.updateById(webinterfaceLogDO);
                logger.error("微信视频号【获取直播大屏数据】接口调用失败！", e);
            }
        }
    }

}